package com.tools.cleanmaster.appinfo;

import android.content.pm.Signature;

import com.tools.cleanmaster.utils.DigestEncodingUtils;
import com.tools.cleanmaster.utils.FileHelper;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;

public class AppSignatureUtils {
    /**
     * Compute signature digest with BaiduSHA1
     * @param cxt
     * @return null will be returned if something wrong happens
     */
    public static String computeSignatureBaiduSha1(Signature[] signatures) {
        if (signatures == null || signatures.length == 0) {
            return null;
        }
        try {
            MessageDigest md = MessageDigest.getInstance("SHA-1");
            md.update(signatures[0].toByteArray());
            return DigestEncodingUtils.encodeHexString(md.digest());
        } catch (NoSuchAlgorithmException e) {
            return null;
        }
    }

    /**
     * Compute signature digest with BaiduMD5
     * @param cxt
     * @return 0 will be returned if something wrong happens
     */
    public static long computeSignatureBaiduMd5(Signature[] signatures) {
        if (signatures == null || signatures.length == 0) {
            return 0;
        }
        byte[] data = signatures[0].toCharsString().getBytes();
        String md5Hex = DigestEncodingUtils.computeMd5HexString(data);
        return createSignatureBaiduMd5(md5Hex);
    }

    private static long createSignatureBaiduMd5(String md5) {
        if (md5 == null || md5.length() < 32) return -1;
        String sign = md5.substring(8, 8 + 16);
        long id1 = 0;
        long id2 = 0;
        String s = "";
        for (int i = 0; i < 8; i++) {
            id2 *= 16;
            s = sign.substring(i, i + 1);
            id2 += Integer.parseInt(s, 16);
        }
        for (int i = 8; i < sign.length(); i++) {
            id1 *= 16;
            s = sign.substring(i, i + 1);
            id1 += Integer.parseInt(s, 16);
        }
        long id = (id1 + id2) & 0xFFFFFFFFL;
        return id;
    }

    /**
     * Compute APK digest with TapasMD5 (Hex encoding)
     * @param apkFilepath
     * @return null may be returned if the APK file not found or other unexpected
     *         exceptions happen
     */
    public static String computeApkTapasMd5(String apkFilepath) {
        File apkFile = new File(apkFilepath);
        if (!apkFile.exists()) {
            return null;
        }

        FileInputStream fis = null;
        try {
            MessageDigest messageDigest = MessageDigest.getInstance("MD5");
            fis = new FileInputStream(apkFile);

            int len;
            byte buffer[] = new byte[32 * 1024]; // 32 KB
            while ((len = fis.read(buffer)) != -1) {
                messageDigest.update(buffer, 0, len);
            }
            return DigestEncodingUtils.encodeHexString(messageDigest.digest());
        } catch (FileNotFoundException e) {
            // nothing to do
        } catch (NoSuchAlgorithmException e) {
            // nothing to do
        } catch (IOException e) {
            // nothing to do
        } finally {
            FileHelper.close(fis);
        }

        return null;
    }

}
